<template>
  <el-drawer title="分配角色" v-model="dialogVisible" size="30%" :destroy-on-close="true">
    <template #default>
      <el-form>
        <el-form-item label="用户姓名">
          <el-input placeholder="请输入用户姓名" v-model="userParams.username" disabled />
        </el-form-item>
        <el-form-item label="角色列表">
          <!-- indeterminate： 为true为半选状态 -->
          <el-checkbox v-model="checkAll" :indeterminate="isIndeterminate" @change="handleCheckAllChange">全选</el-checkbox>
          <el-checkbox-group v-model="userRole" @change="handleCheckedCitiesChange">
            <el-checkbox v-for="(role, index) in allRole" :key="index" :label="role">{{ role.roleName }}</el-checkbox>
          </el-checkbox-group>
        </el-form-item>
      </el-form>
    </template>

    <template #footer>
      <div style="flex: auto">
        <el-button @click="cancel">取消</el-button>
        <el-button type="primary" @click="save" v-loading="loading">确认</el-button>
      </div>
    </template>
  </el-drawer>
</template>

<script setup lang="ts">
  import { ref } from 'vue'
  import { reqAllRole, reqSetUserRole } from '@/api/acl/user'
  import type { AllRole, AllRoleResponseData, User } from '@/api/acl/user/type'
  import { getElMessage } from '@/utils/message'

  const dialogVisible = ref<boolean>(false)
  const loading = ref<boolean>(false)
  const userParams = ref<User>({
    username: '',
  })
  const checkAll = ref<boolean>(false)
  const isIndeterminate = ref<boolean>(true)
  const userRole = ref<AllRole>([])
  const allRole = ref<AllRole>([])
  function open(user: User) {
    dialogVisible.value = true
    userParams.value = user
    getAllRole(user)
  }

  const $emits = defineEmits(['reload'])
  async function save() {
    try {
      const userRoles = {
        userId: userParams.value.id as number,
        roleIdList: userRole.value.map((o) => o.id) as number[],
      }
      const res: any = await reqSetUserRole(userRoles)
      if (res.code === 200) {
        getElMessage('分配角色成功', 'success')
      } else {
        getElMessage('分配角色失败', 'error')
      }
    } catch (error) {
      getElMessage((error as Error).message, 'error')
    } finally {
      dialogVisible.value = false
      $emits('reload')
    }
  }

  async function getAllRole(user: User) {
    try {
      const res: AllRoleResponseData = await reqAllRole(user.id as number)
      if (res.code === 200) {
        allRole.value = res.data.allRolesList
        userRole.value = res.data.assignRoles

        isIndeterminate.value = false
        checkAll.value = allRole.value.length === userRole.value.length
      }
    } catch (error) {
      getElMessage((error as Error).message, 'error')
    }
  }

  const handleCheckAllChange = (val: boolean) => {
    userRole.value = val ? allRole.value : []
    isIndeterminate.value = false
  }

  const handleCheckedCitiesChange = (value: string[]) => {
    const checkedCount = value.length
    checkAll.value = checkedCount === allRole.value.length
    isIndeterminate.value = checkedCount > 0 && checkedCount < allRole.value.length
  }

  function cancel() {
    dialogVisible.value = false
  }
  defineExpose({
    open,
  })
</script>

<style lang="scss" scoped>
  .el-checkbox {
    width: 100%;
  }
</style>
